/*
 *  This file is part of AtlasMapper server and clients.
 *
 *  Copyright (C) 2012 Australian Institute of Marine Science
 *
 *  Contact: Gael Lafond <g.lafond@aims.org.au>
 *
 *  This program is free software: you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation, either version 3 of the License, or
 *  (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License
 *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */
package au.gov.aims.metadatagenerator.exporter;

import java.util.HashSet;
import java.util.Random;
import java.util.Set;

/**
 * Generate valid XSD ID, similar to the one generated by GeoNetwork and following the rules in:
 *     http://www.schemacentral.com/sc/xsd/t-xsd_ID.html
 * Examples:
 *     d27731703b4066feda
 *     d4badef7f154f06fe0
 *     dcfd52aec528ab954f
 *     d92f1329a69e6d4e58
 *     d2e7aafa1e730b7f8b
 *     dfc98b5641910f5045
 * NOTE: Use no more than one generator per XML document to ensure the uniqueness of IDs in the document.
 *
 * GeoNetwork use generate-id(), a XSLT built-in function:
 *     http://www.w3schools.com/xsl/func_generateid.asp
 *     I could not find the source of that function so I implemented my own.
 * Examples from GeoNetwork:
 *     d15655e176a1050910
 *     d42171e203a1050910
 *     d28761e187a1050910
 *     It seems to follow the following pattern: "dXXXXXeXXXa1050910"
 */
public class XsdIdGenerator {
	private Set<String> existingXsdIds = new HashSet<String>();

	public String getNewXsdId() {
		String newXsdId;
		do {
			// The ID must start with a letter (or underscore). GeoNetwork seems to have chosen "d" as a starting letter.
			newXsdId = "d" + getRandomHexString(17);
		} while(this.existingXsdIds.contains(newXsdId));

		this.existingXsdIds.add(newXsdId);
		return newXsdId;
	}

	private static String getRandomHexString(int numChars) {
		Random random = new Random();
		StringBuffer sb = new StringBuffer();
		while(sb.length() < numChars){
			sb.append(Integer.toHexString(random.nextInt()));
		}

		return sb.toString().substring(0, numChars);
	}
}
